package service.impl;

import exception.BusinessException;
import model.DifferOrder;
import model.LogEntity;
import model.OrderModificationRequest;
import model.entity.Item;
import model.entity.Order;
import model.enums.ExceptionCode;
import model.enums.ModifyType;
import model.enums.OrderStatus;
import service.IModifyOrderService;
import service.OrderRepository;
import service.OrderService;
import utils.ItemUtil;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Objects;

/**
 * @Author WeiJin
 * @Version 1.0
 * @Date 2025/3/27 14:24
 */
public class ModifyOrderServiceImpl implements IModifyOrderService {

    private OrderRepository orderRepository;
    private SimpleOrderService orderService;

    public ModifyOrderServiceImpl() {
        this.orderRepository = new MemoryOrderRepository();
        this.orderService = new SimpleOrderService(this.orderRepository);
    }

    @Override
    public Order modifyOrder(String orderId, OrderModificationRequest request, boolean isAgree) {
        Order order = this.orderRepository.findById(orderId);

        // 旧订单非空判断
        if (Objects.isNull(order)) {
            throw new BusinessException(ExceptionCode.ORDER_IS_NULL);
        }
        // 订单状态判断
        OrderStatus oldOrderStatus = order.getStatus();
        // 已支付的订单禁止修改
        if (OrderStatus.PAID.equals(oldOrderStatus)) {
            throw new BusinessException(ExceptionCode.MODIFY_FORBIDDEN);
        }

        //校验商品有效性
        //获取菜单(所有商品)
        List<Item> menu = ItemUtil.getMenu();
        if ( !new HashSet<>(menu).containsAll(request.getItems())){
            throw new BusinessException(ExceptionCode.HAS_INVALID_ITEM);
        }
        // 记录旧商品，以免商家不同意修改，还原商品
        List<Item> orderItems = new ArrayList<>(order.getItems());

        // 差异单
        DifferOrder differOrder = new DifferOrder(orderId, order.getItems(),
                order.getTotalPrice(), request.getModifyType());

        // 3. 处理不同类型的修改
        switch (request.getModifyType()) {
            case FULL_REPLACE:
                // 处理整单替换逻辑
                // 替换所有商品
                order.setItems(request.getItems());
                break;
            // 处理部分修改逻辑
            case ADD:
                // 新增商品
                // 获取原商品并把新的商品追加上去
                List<Item> notAddItems = order.getItems();
                notAddItems.addAll(request.getItems());
                break;
            case DELETE:
                // 删除商品
                List<Item> notDelItems = order.getItems();
                notDelItems.removeAll(request.getItems());
                break;
            case UPDATE:
                break;
            default:
                throw new IllegalArgumentException("Invalid modify type");
        }

        // 商家审批
        if (isAgree) {
            // 同意修改
            // 设置修改时间
            order.setCreateTime(LocalDateTime.now());
            // 修改订单状态为已修改
            order.setStatus(OrderStatus.MODIFIED);
        } else {
            // 商家不同意
            // 还原商品
            order.setItems(orderItems);
        }
        // 重新计算总价
        double totalPrice = this.orderService
                .calculateTotalPrice(order, order.getItems(),
                        false, LocalDateTime.now());
        order.setTotalPrice(totalPrice);
        // 补全差异单
        differOrder.setNewItems(order.getItems());
        differOrder.setNewPrice(order.getTotalPrice());

        // 构建日志
        LogEntity logEntity = new LogEntity(LocalDateTime.now(), differOrder);
        logEntity.setAgree(isAgree);

        // 8. 执行修改
        this.orderRepository.save(order);

        // 9. 记录操作日志
        orderRepository.logModification(orderId, logEntity);

        return this.orderRepository.findById(order.getOrderId());
    }


}
